﻿using SimMetrics.Net.Metric;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace AspDotNet.Framework.MarkdownParser
{
    public partial class Form2 : Form
    {
        Levenstein LevensteinInstance = new SimMetrics.Net.Metric.Levenstein();

        public Form2()
        {
            InitializeComponent();
            hNextClipboardViewer = (IntPtr)SetClipboardViewer((int)this.Handle);
        }

        #region [关于C#监视剪贴板信息_于大大大洋的博客-CSDN博客_c# 监听剪切板变化](https://blog.csdn.net/arrowzz/article/details/56689111)
        [DllImport("user32.dll")]
        protected static extern int SetClipboardViewer(int hWndViewer);
        [DllImport("user32.dll")]
        protected static extern bool ChangeClipboardChain(IntPtr hWndResume, IntPtr hWndNext);
        [DllImport("user32.dll")]
        protected static extern int SendMessage(IntPtr hWnd, int nMsg, IntPtr wParam, IntPtr lParam);
        IntPtr hNextClipboardViewer;//下一个监视的窗口
        void SendNotify()
        {
            if (Clipboard.ContainsText())
            {
                richTextBoxOrgin.Text = Clipboard.GetText();
                Console.WriteLine(richTextBoxOrgin.Text);
            }
        }
        protected override void WndProc(ref Message m)
        {
            const int WM_DRAWCLPBORAD = 0x308;
            const int WM_CHANGCBCHAIN = 0X030D;
            switch (m.Msg)
            {
                case WM_DRAWCLPBORAD:
                    if (Clipboard.ContainsText())
                    {//包含文本格式
                        SendNotify();
                    }
                    SendMessage(hNextClipboardViewer, m.Msg, m.WParam, m.LParam);
                    break;
                case WM_CHANGCBCHAIN:
                    if (hNextClipboardViewer == m.WParam)
                    {//更新要发送消息的下一个窗口的句柄
                        hNextClipboardViewer = m.LParam;
                    }
                    else
                    {
                        SendMessage(hNextClipboardViewer, m.Msg, m.WParam, m.LParam);
                    }
                    break;
                default:
                    base.WndProc(ref m);
                    break;
            }
        }

        protected override void OnClosed(EventArgs e)
        {
            if (components != null)
            {
                ChangeClipboardChain(this.Handle, hNextClipboardViewer);
                components.Dispose();
            }
            base.OnClosed(e);
        }
        #endregion



        private void richTextBoxOrgin_TextChanged(object sender, EventArgs e)
        {
            if (!string.IsNullOrWhiteSpace(richTextBoxOrgin.Text))
            {
                string result = Regex.Replace(richTextBoxOrgin.Text, @"\[(.+?)\]\(.+?\)", "$1");

                result = Regex.Replace(result, @"\*(\w+?)\*", "$1");
                result = Regex.Replace(result, @"(?<g1>\*+)(.+?)\k'g1'", "$1");

                richTextBoxParse.Text = result;
            }
        }

        private void Form1_Activated(object sender, EventArgs e)
        {
            var data = Clipboard.GetText();
            richTextBoxOrgin.Text = data;
        }

        private void richTextBoxParse_TextChanged(object sender, EventArgs e)
        {
            try
            {
                string controlText = richTextBoxParse.Text;
                string clipBoardText = Clipboard.GetText();
                if (!string.IsNullOrWhiteSpace(controlText))
                {
                    if (controlText != clipBoardText
                        || (controlText.Length > 100 && LevensteinInstance.GetSimilarity(controlText, clipBoardText) > 0.98))
                    {
                        Clipboard.Clear();
                        Clipboard.SetText(controlText);
                    }
                }
            }
            catch (Exception ex)
            {
                Task.Factory.StartNew(() =>
                {
                    MessageBox.Show(ex.ToString());
                });
            }
        }

        static decimal Similarigy(string source, string target)
        {
            int n = source.Length;
            int m = target.Length;
            int[,] d = new int[n + 1, m + 1];

            if (n == 0) return m;
            if (m == 0) return n;
            for (int i = 0; i <= n; d[i, 0] = i++) { }
            for (int j = 0; j <= m; d[0, j] = j++) { }
            for (int i = 1; i <= n; i++)
            {
                for (int j = 1; j <= m; j++)
                {
                    int cost = (target[j - 1] == source[i - 1]) ? 0 : 1;

                    d[i, j] = Math.Min(Math.Min(d[i - 1, j] + 1, d[i, j - 1] + 1), d[i - 1, j - 1] + cost);
                }
            }
            return 1 - (decimal)d[n, m] / source.Length;
        }
    }
}
